//
// Created by kyle on 25-7-16.
//

#ifndef FONTRENDERER_H
#define FONTRENDERER_H


#include <ft2build.h>
#include FT_FREETYPE_H
#include <freetype/ftglyph.h>
#include <string>
#include <filesystem>
#include <memory>
#include <system_error>
#include "FrameBuffer.h"
#include "GlyphMetrics.h"

namespace fs = std::filesystem;

class FrameBuffer; // 前向声明

class FontRenderer {
private:
    struct FT_FaceDeleter {
        void operator()(FT_Face face) const {
            if (face) FT_Done_Face(face);
        }
    };

    using UniqueFTFace = std::unique_ptr<std::remove_pointer_t<FT_Face>, FT_FaceDeleter>;

    FT_Library library_ = nullptr;
    UniqueFTFace chinese_face_;

    bool load_font(const std::string &path, UniqueFTFace &face, const std::string &type) const;

    static std::string find_system_chinese_font();

public:

    // 使用RAII管理资源
    explicit FontRenderer() {
        if (!init()) {
            throw std::runtime_error("Font initialization failed");
        }
    }

    ~FontRenderer();

    bool init();

    void draw_text(std::shared_ptr<FrameBuffer> fb, const std::string &text, int x, int y,
                   uint8_t r, uint8_t g, uint8_t b, int font_size, bool is_chinese) const;

    // 禁用拷贝和赋值
    FontRenderer(const FontRenderer &) = delete;

    FontRenderer &operator=(const FontRenderer &) = delete;


    GlyphMetrics get_glyph_metrics(uint32_t char_code, int font_size, bool is_chinese) {
        FT_Face face = get_face(is_chinese);
        if (!face) return {0, 0, 0, 0, 0};

        FT_Set_Pixel_Sizes(face, 0, font_size);
        // FT_Set_Char_Size(face, 0, font_size << 6, 96, 96);

        if (FT_Load_Char(face, char_code, FT_LOAD_RENDER | FT_LOAD_TARGET_MONO)) {
            return {0, 0, 0, 0, 0};
        }

        return {
            static_cast<int>(face->glyph->bitmap.width),
            static_cast<int>(face->glyph->bitmap.rows),
            static_cast<int>(face->glyph->bitmap_left), // 水平起始位置
            static_cast<int>(face->glyph->bitmap_top), // 垂直起始位置(从基线到顶部)
            static_cast<int>(face->glyph->advance.x >> 6)
        };
    }

    /**
     * 渲染文字
     * @param fb
     * @param char_code
     * @param x
     * @param y
     * @param color
     * @param font_size
     * @param is_chinese
     */
    void render_char(std::shared_ptr<FrameBuffer> fb, uint32_t char_code, int x, int y,
                     uint16_t color, int font_size, bool is_chinese);

    /**
     * 这个字符是否是中文字符
     * @param char_code
     * @return
     */
    bool is_chinese_char(uint32_t char_code);

    /**
     * 获取字体 高度/宽度的比率
     * @return
     */
    double get_font_radio();

    FT_Face get_face(bool is_chinese = true) {
        return chinese_face_.get();
    }
};


#endif //FONTRENDERER_H
